﻿using KAs.Application.Contract.Svc;
using KAs.SqlSugar.Entity;
using KAs.SqlSugar.Entity.Interface;
using Microsoft.AspNetCore.Mvc.Filters;
using Microsoft.Extensions.DependencyInjection;
using SqlSugar;
using System.Linq.Dynamic.Core;
using System.Linq.Expressions;

namespace KAs.Filter;

public class ActionFilter : IActionFilter
{
    // 目前该处主要实现db的相关审计配置
    public void OnActionExecuting(ActionExecutingContext context)
    {
        var db = context.HttpContext.RequestServices.GetService<ISqlSugarClient>();
        var currentUserInfo = context.HttpContext.RequestServices.GetService<ICurrentUserInfo>();
        var assemblies = context.HttpContext.RequestServices.GetService<IAssembliesService>();
        var userInfo = currentUserInfo.GetUserInfo();
        var entities = assemblies.GetEntities();

        // 全局添加软删除过滤
        foreach (var entityType in entities.Where(x => typeof(IDeleteEntity).IsAssignableFrom(x)).ToList())
        {
            var lambda = DynamicExpressionParser
                .ParseLambda(new[] { Expression.Parameter(entityType, "tb") }, typeof(bool), $"tb.IsDeleted == @0", false);
            // 注意此处添加后，联查时不再支持类似IQueryable<T1,T2>(exp)的语法，请使用.InnerJoin<T2>(exp)等
            db.QueryFilter.Add(new TableFilterItem<object>(entityType, lambda, true));
        }
        //单例参数配置，所有上下文生效
        // sql执行前
        db.Aop.OnLogExecuting = (sql, pars) =>
        {
            //Console.WriteLine(sql);//输出sql
        };
        // sql执行后
        db.Aop.OnLogExecuted = (sql, pars) =>
        {
            //Console.WriteLine(sql);//输出sql
        };
        // 发生异常时
        db.Aop.OnError = ex =>
        {
            // 输出日志
        };
        // 差异审计
        db.Aop.OnDiffLogEvent = diffEvent =>
        {
            // 操作数据时仅调用EnableDiffLogEvent()方法才会进行差异审计，其中BusinessData为参数值
            if (Convert.ToBoolean(diffEvent.BusinessData))
            {
                // 记录数据变化
                var newLog = new SimpleDiffLog()
                {
                    TableName = diffEvent.BeforeData.Any() ? diffEvent.BeforeData[0].TableName : string.Empty,
                    DiffType = diffEvent.DiffType.ToString(),
                    BeforeData = diffEvent.BeforeData,
                    AfterData = diffEvent.AfterData,
                    Sql = diffEvent.Sql
                };
                db.Insertable(newLog).ExecuteReturnSnowflakeId();
            }
        };
        // 数据过滤器，用于添加默认值
        db.Aop.DataExecuting = (oldValue, entityInfo) =>
        {
            // inset生效
            if (entityInfo.PropertyName == "CreateTime" && entityInfo.OperationType == DataFilterType.InsertByObject)
            {
                entityInfo.SetValue(DateTime.Now);//修改CreateTime字段
            }
            if (entityInfo.PropertyName == "CreateUid" && entityInfo.OperationType == DataFilterType.InsertByObject && userInfo != null)
            {
                entityInfo.SetValue(userInfo.Uid);
            }
            // update生效        
            if (entityInfo.PropertyName == "UpdateTime" && entityInfo.OperationType == DataFilterType.UpdateByObject)
            {
                entityInfo.SetValue(DateTime.Now);//修改UpdateTime字段
            }
            // update生效        
            if (entityInfo.PropertyName == "UpdateUid" && entityInfo.OperationType == DataFilterType.UpdateByObject && userInfo != null)
            {
                entityInfo.SetValue(userInfo.Uid);
            }

            //根据当前列修改另一列 可以么写
            //if(当前列逻辑==XXX)
            //var properyDate = entityInfo.EntityValue.GetType().GetProperty("Date");
            //if(properyDate!=null)
            //properyDate.SetValue(entityInfo.EntityValue,1);
        };
    }

    public void OnActionExecuted(ActionExecutedContext context)
    {
    }
}
